package cn.lx.middleware.thread.pool.sdk.trigger.job;

import cn.lx.middleware.thread.pool.sdk.domain.model.entity.ThreadPoolConfigEntity;
import cn.lx.middleware.thread.pool.sdk.domain.model.valobj.RegistryEnumVO;
import io.micrometer.core.instrument.Gauge;
import io.micrometer.core.instrument.MeterRegistry;
import org.redisson.api.RList;
import org.redisson.api.RedissonClient;
import org.slf4j.Logger;
import org.springframework.scheduling.annotation.Scheduled;

import javax.annotation.PostConstruct;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @author wcy
 * @version 1.0
 * @description: 线程池指标监控任务
 * @date 2025-06-13 下午1:06
 */
public class ThreadPoolMetricsJob {


    private static final Logger log = org.slf4j.LoggerFactory.getLogger(ThreadPoolMetricsJob.class);

    private RedissonClient redissonClient;

    private MeterRegistry meterRegistry;


    public ThreadPoolMetricsJob(RedissonClient redissonClient, MeterRegistry meterRegistry) {
        this.redissonClient = redissonClient;
        this.meterRegistry = meterRegistry;
    }

    private final Map<String, Gauge> gaugeMap = new ConcurrentHashMap<>();

    @PostConstruct
    public void init() {
        // 初始化时注册所有指标
        registerMetrics();
    }

    @Scheduled(fixedRate = 10000) // 每10秒执行一次
    public void collectMetrics() {
        try {
            // 获取所有线程池配置
            RList<ThreadPoolConfigEntity> cacheList = redissonClient.getList(RegistryEnumVO.THREAD_POOL_CONFIG_LIST_KEY.getKey());
            List<ThreadPoolConfigEntity> threadPoolList = cacheList.readAll();

            // 更新指标
            for (ThreadPoolConfigEntity config : threadPoolList) {
                String appName = config.getAppName();
                String threadPoolName = config.getThreadPoolName();
                log.info("监控上报更新指标：{}", config);
                // 更新或创建指标
                updateGauge(appName, threadPoolName, "core_pool_size", config.getCorePoolSize());
                updateGauge(appName, threadPoolName, "maximum_pool_size", config.getMaximumPoolSize());
                updateGauge(appName, threadPoolName, "active_count", config.getActiveCount());
                updateGauge(appName, threadPoolName, "pool_size", config.getPoolSize());
                updateGauge(appName, threadPoolName, "queue_size", config.getQueueSize());
                updateGauge(appName, threadPoolName, "remaining_capacity", config.getRemainingCapacity());
            }
        } catch (Exception e) {
            log.error("收集线程池指标异常", e);
        }
    }

    private void updateGauge(String appName, String threadPoolName, String metricName, Number value) {
        String gaugeName = String.format("thread_pool_%s", metricName);

        Gauge.builder(gaugeName, () -> value)
                .tag("app_name", appName)
                .tag("thread_pool_name", threadPoolName)
                .description(String.format("Thread pool %s metric", metricName))
                .register(meterRegistry) ;
    }

    private void registerMetrics() {
        // 注册所有可能的指标
        String[] metricNames = {
                "core_pool_size",
                "maximum_pool_size",
                "active_count",
                "pool_size",
                "queue_size",
                "remaining_capacity"
        };

        for (String metricName : metricNames) {
            String gaugeName = String.format("thread_pool_%s", metricName);
            Gauge.builder(gaugeName, () -> 0)
                    .tag("app_name", "placeholder")
                    .tag("thread_pool_name", "placeholder")
                    .description(String.format("Thread pool %s metric", metricName))
                    .register(meterRegistry);
        }
    }
}
